﻿using System;
using System.Collections.Generic;
using System.Collections.Specialized;
using System.Diagnostics;
using System.Linq;
using RayDen.Library.Core.Primitives;
using RayDen.Library.Data.Imaging;
using RayDen.Library.Entity.Scene;

namespace RayDen.Library.Data {
    [Obsolete]
    public class TextureAtlas {
        private readonly Dictionary<string, Tuple<TextureInfo, ITexture>> textures;

        public ITexture this[string name] {
            get {
                Tuple<TextureInfo, ITexture> value;
                return this.textures.TryGetValue(name, out value) ? value.Item2 : null;
            }
        }


        public TextureAtlas() {
            textures = new Dictionary<string, Tuple<TextureInfo, ITexture>>();
        }

        public void AddTexture(TextureInfo texture) {
            if (this.textures.ContainsKey(texture.Name))
                return;
            if (texture is ImageTextureInfo) {
                this.textures.Add(texture.Name, new Tuple<TextureInfo, ITexture>(texture, 
                    //new NoiseTexture(512, 512, new RgbSpectrum(1f)))
                    ImageFactory.FreeImageLoadBitmap((texture as ImageTextureInfo).FilePath))
                    
                    );
            }
            else if (texture is ConstTextureInfo) {
                this.textures.Add(texture.Name, new Tuple<TextureInfo, ITexture>(texture, new ConstSpectrumTexture((texture as ConstTextureInfo).Color, 0, 0)));
            } else if (texture is SolidTextureInfo)
            {
                this.textures.Add(texture.Name, new Tuple<TextureInfo, ITexture>(texture, new NoiseTexture(512,512, RgbSpectrum.UnitSpectrum())));
            }
        }

        public void Clear() {
            foreach(var texture in textures.Values) {
                texture.Item2.Dispose();
            }
            textures.Clear();
        }

    }


    public class OptimizedTextureAtlas
    {
        private int CurrentID;
        private readonly List<Tuple<TextureInfo, ITexture>> textures;
        private readonly Dictionary<string, int> nameIDMap;

        public ITexture this[int id]
        {
            get
            {
                return this.textures[id].Item2;
            }
        }


        
        public OptimizedTextureAtlas()
        {
            textures = new List<Tuple<TextureInfo, ITexture>>();
            CurrentID = 0;
            nameIDMap = new Dictionary<string, int>();
        }

        public int AddTexture(TextureInfo texture)
        {
            if (this.nameIDMap.ContainsKey(texture.Name))
                return nameIDMap[texture.Name];

            nameIDMap.Add(texture.Name, CurrentID++);

            if (texture is ImageTextureInfo)
            {
                this.textures.Add(new Tuple<TextureInfo, ITexture>(texture,
                    //new NoiseTexture(512, 512, new RgbSpectrum(1f)))
                    ImageFactory.FreeImageLoadBitmap((texture as ImageTextureInfo).FilePath))
                    );
            }
            else if (texture is ConstTextureInfo)
            {
                this.textures.Add(new Tuple<TextureInfo, ITexture>(texture, new ConstSpectrumTexture((texture as ConstTextureInfo).Color, 0, 0)));
            }
            else if (texture is SolidTextureInfo)
            {
                this.textures.Add(new Tuple<TextureInfo, ITexture>(texture, new NoiseTexture(512, 512, RgbSpectrum.UnitSpectrum())));
            } 

            return CurrentID-1;
        }



      
        public void Clear()
        {
            foreach (var texture in textures)
            {
                texture.Item2.Dispose();
            }

            nameIDMap.Clear();
            CurrentID = 0;
            textures.Clear();
        }

        public bool Contains(TextureInfo tx)
        {
            return
                this.textures.Any(
                    item =>
                        item.Item1.GetType() == tx.GetType() &&
                                    item.Item1.Name.Equals(tx.Name, StringComparison.InvariantCultureIgnoreCase));
        }
    }
}
